﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Xna.Framework.Content;
using Microsoft.Xna.Framework;

namespace Qreed.Xna.Font
{
    public class VectorFontReader : ContentTypeReader<VectorFont>
    {
        /// <summary>
        /// Reads a strongly typed object from the current stream.
        /// </summary>
        /// <param name="input">The ContentReader used to read the object.</param>
        /// <param name="existingInstance">An existing object to read into.</param>
        /// <returns></returns>
        protected override VectorFont Read(ContentReader input, VectorFont existingInstance)
        {
            VectorFont vectorFont = new VectorFont();

            vectorFont.FontName = input.ReadString();
            vectorFont.LineHeight = input.ReadSingle();

            // Read the character list

            while (true)
            {
                char key = input.ReadChar();

                if (key == '\0')
                    break;

                VectorFontCharacter character = ReadCharacter(vectorFont, input, key);
                vectorFont.CharacterMap.Add(key, character);
            }

            int kerningCount = input.ReadInt32();

            for (int i = 0; i < kerningCount; i++)
            {
                VectorFontCharacterKerningPair k = new VectorFontCharacterKerningPair(input.ReadChar(), input.ReadChar());
                Vector2 v = input.ReadObject<Vector2>();

                vectorFont.KerningTable.Add(k, v);
            }

            return vectorFont;
        }

        private static VectorFontCharacter ReadCharacter(VectorFont vectorFont, ContentReader input, char key)
        {
            VectorFontCharacter character = new VectorFontCharacter(vectorFont);

            character.Character = key;

            character.BoundingBox = input.ReadObject<BoundingBox>();
            character.Advancement = input.ReadObject<Vector2>();
            character.Vertices = input.ReadObject<List<Vector2>>().ToArray();

            // Read the outlines
            ReadCharacterOutlines(input, character);

            // Read the triangles
            ReadTriangles(input, character);


            return character;
        }

        private static void ReadTriangles(ContentReader input, VectorFontCharacter character)
        {
            int triangleCount = input.ReadInt32();
            character.Triangles = new VectorFontCharacterTriangle[triangleCount];

            for (int i = 0; i < triangleCount; i++)
                character.Triangles[i] = new VectorFontCharacterTriangle(input.ReadInt32(), input.ReadInt32(), input.ReadInt32());
        }

        private static void ReadCharacterOutlines(ContentReader input, VectorFontCharacter character)
        {
            int outlineCount = input.ReadInt32();
            character.Outlines = new VectorFontCharacterOutline[outlineCount];

            for (int i = 0; i < outlineCount; i++)
                character.Outlines[i] = new VectorFontCharacterOutline(input.ReadInt32(), input.ReadInt32(), input.ReadBoolean());
        }
    }
}
